import json
from django.shortcuts import render, HttpResponse
from django.http import JsonResponse
from django.forms import model_to_dict
from django.views.decorators.csrf import csrf_exempt
from django.urls import reverse
from django.http import StreamingHttpResponse, FileResponse

import requests

from web.forms.file import FolderModelForm, FileModelForm
from web import models

from utils.tencent.cos import delete_file, delete_file_list, credential


def file(request, project_id):
    parent_object = None
    folder_id = request.GET.get('folder', '')
    if folder_id.isdecimal():
        parent_object = models.FileRepository.objects.filter(id=int(folder_id), file_type=2,
                                                             project=request.tracer.project).first()
    # GET查看页面
    if request.method == 'GET':
        breadcrumb_list = []
        parent = parent_object
        while parent:
            breadcrumb_list.insert(0, {'id': parent.id, 'name': parent.name})
            parent = parent.parent
        queryset = models.FileRepository.objects.filter(project=request.tracer.project, )
        if parent_object:
            file_object_list = queryset.filter(parent=parent_object).order_by('-file_type')
        else:
            file_object_list = queryset.filter(parent__isnull=True).order_by('-file_type')

        form = FolderModelForm(request, parent_object)
        context = {
            'form': form,
            "file_object_list": file_object_list,
            "breadcrumb_list": breadcrumb_list,
            'folder_object': parent_object
        }
        return render(request, 'file.html', context)

    # POST添加文件&修改文件
    fid = request.POST.get('fid', '')
    edit_object = None
    if fid.isdecimal():
        edit_object = models.FileRepository.objects.filter(id=int(fid), file_type=2,
                                                           project=request.tracer.project).first()
    if edit_object:
        # 修改
        form = FolderModelForm(request, parent_object, data=request.POST, instance=edit_object)
    else:
        # 添加
        form = FolderModelForm(request, parent_object, data=request.POST)

    if form.is_valid():
        form.instance.project = request.tracer.project
        form.instance.file_type = 2
        form.instance.update_user = request.tracer.user
        form.instance.parent = parent_object
        form.save()
        return JsonResponse({'status': True})

    return JsonResponse({'status': False, 'error': form.errors})


def file_delete(request, project_id):
    fid = request.GET.get('fid')
    delete_object = models.FileRepository.objects.filter(id=fid, project_id=project_id).first()
    if delete_object.file_type == 1:
        # 更新项目已用空间
        request.tracer.project.use_space -= delete_object.file_size
        request.tracer.project.save()

        # cos中删除文件
        delete_file(request.tracer.project.bucket, request.tracer.project.region, delete_object.key)

        # 数据库中删除文件
        delete_object.delete()
        return JsonResponse({'status': True})


    else:
        # models.FileRepository.objects.filter(parent=delete_object)
        total_size = 0
        folder_list = [delete_object, ]
        key_list = []
        for folder in folder_list:
            child_list = models.FileRepository.objects.filter(project_id=project_id, parent=folder).order_by(
                '-file_type')
            for child in child_list:
                if child.file_type == 2:
                    folder_list.append(child)
                else:
                    total_size += child.file_size

                    key_list.append({'Key': child.key})

        if key_list:
            delete_file_list(request.tracer.project.bucket, request.tracer.project.region, key_list)

        if total_size:
            request.tracer.project.use_space -= total_size
            request.tracer.project.save()

        delete_object.delete()
        return JsonResponse({'status': True})


@csrf_exempt
def cos_credential(request, project_id):
    """ 获取cos上传临时凭证 """
    per_file_limit = request.tracer.price_policy.per_file_size * 1024 * 1024
    total_file_limit = request.tracer.price_policy.project_space * 1024 * 1024 * 1024

    total_size = 0
    file_list = json.loads(request.body.decode('utf-8'))
    for item in file_list:
        # 文件的字节大小 item['size'] = B
        # 单文件限制的大小 M
        # 超出限制
        if item['size'] > per_file_limit:
            msg = "单文件超出限制（最大{}M），文件：{}，请升级套餐。".format(request.tracer.price_policy.per_file_size, item['name'])
            return JsonResponse({'status': False, 'error': msg})
        total_size += item['size']

        # 做容量限制：单文件 & 总容量

    # 总容量进行限制
    # request.tracer.price_policy.project_space  # 项目的允许的空间
    # request.tracer.project.use_space # 项目已使用的空间
    if request.tracer.project.use_space + total_size > total_file_limit:
        return JsonResponse({'status': False, 'error': "容量超过限制，请升级套餐。"})

    data_dict = credential(request.tracer.project.bucket, request.tracer.project.region)
    return JsonResponse({'status': True, 'data': data_dict})


@csrf_exempt
def file_post(request, project_id):
    form = FileModelForm(request, data=request.POST)
    if form.is_valid():
        data_dict = form.cleaned_data
        data_dict.pop('etag')
        data_dict.update({'project': request.tracer.project, 'file_type': 1, 'update_user': request.tracer.user})
        instance = models.FileRepository.objects.create(**data_dict)

        request.tracer.project.use_space += data_dict['file_size']
        request.tracer.project.save()

        result = {
            'id': instance.id,
            'name': instance.name,
            'file_type': instance.get_file_type_display(),
            'username': instance.update_user.username,
            'datetime': instance.update_datetime.strftime('%Y年%m月%d日 %H:%M'),
            'file_size': instance.file_size,
            'download_url':reverse('file_download',kwargs={'project_id':project_id,'file_id':instance.id})
        }
        return JsonResponse({'status': True, 'data': result})

    return JsonResponse({'status': False, 'data': '文件错误'})


def file_download(request,project_id,file_id):
    # 打开文件，获取文件的内容
    # with open('xxx.png', mode="rb") as f:
    #     data = f.read()
    file_object = models.FileRepository.objects.filter(id=file_id,project_id=project_id).first()
    res = requests.get(file_object.file_path)
    data=res.content

    response = HttpResponse(data)
    # 设置响应头
    response['Content-Disposition'] = "attachment; filename={}".format(file_object.name)
    return response
